/*   1:    */ package com.atomikos.datasource.xa.session;
/*   2:    */ 
/*   3:    */ import com.atomikos.datasource.xa.XATransactionalResource;
/*   4:    */ import com.atomikos.icatch.CompositeTransaction;
/*   5:    */ import com.atomikos.icatch.HeuristicMessage;
/*   6:    */ import com.atomikos.icatch.system.Configuration;
/*   7:    */ import java.util.ArrayList;
/*   8:    */ import java.util.HashSet;
/*   9:    */ import java.util.Iterator;
/*  10:    */ import java.util.List;
/*  11:    */ import java.util.Set;
/*  12:    */ import javax.transaction.xa.XAResource;
/*  13:    */ 
/*  14:    */ public class SessionHandleState
/*  15:    */ {
/*  16:    */   private TransactionContext currentContext;
/*  17:    */   private Set allContexts;
/*  18:    */   private XATransactionalResource resource;
/*  19:    */   private XAResource xaResource;
/*  20:    */   private boolean erroneous;
/*  21:    */   private boolean closed;
/*  22: 59 */   private List sessionHandleStateChangeListeners = new ArrayList();
/*  23:    */   
/*  24:    */   public SessionHandleState(XATransactionalResource resource, XAResource xaResource)
/*  25:    */   {
/*  26: 64 */     this.resource = resource;
/*  27: 65 */     this.xaResource = xaResource;
/*  28: 66 */     this.allContexts = new HashSet();
/*  29: 67 */     this.erroneous = false;
/*  30: 68 */     this.closed = true;
/*  31:    */   }
/*  32:    */   
/*  33:    */   public synchronized boolean isTerminated()
/*  34:    */   {
/*  35: 81 */     boolean terminated = true;
/*  36: 82 */     Iterator it = this.allContexts.iterator();
/*  37: 83 */     while (it.hasNext())
/*  38:    */     {
/*  39: 84 */       TransactionContext b = (TransactionContext)it.next();
/*  40: 85 */       if (b.isTerminated()) {
/*  41: 86 */         it.remove();
/*  42:    */       } else {
/*  43: 88 */         terminated = false;
/*  44:    */       }
/*  45:    */     }
/*  46: 91 */     if (terminated) {
/*  47: 91 */       this.currentContext = null;
/*  48:    */     }
/*  49: 93 */     return terminated;
/*  50:    */   }
/*  51:    */   
/*  52:    */   public synchronized void notifySessionBorrowed()
/*  53:    */   {
/*  54:103 */     if (Configuration.isDebugLoggingEnabled()) {
/*  55:103 */       Configuration.logDebug(this + ": notifySessionBorrowed");
/*  56:    */     }
/*  57:104 */     this.currentContext = new TransactionContext(this.resource, this.xaResource);
/*  58:105 */     this.allContexts.add(this.currentContext);
/*  59:106 */     this.closed = false;
/*  60:    */   }
/*  61:    */   
/*  62:    */   public void notifySessionClosed()
/*  63:    */   {
/*  64:117 */     if (Configuration.isDebugLoggingEnabled()) {
/*  65:117 */       Configuration.logDebug(this + ": entering notifySessionClosed");
/*  66:    */     }
/*  67:118 */     boolean notifyOfClosedEvent = false;
/*  68:120 */     synchronized (this)
/*  69:    */     {
/*  70:121 */       boolean alreadyTerminated = isTerminated();
/*  71:122 */       Iterator it = this.allContexts.iterator();
/*  72:123 */       while (it.hasNext())
/*  73:    */       {
/*  74:124 */         TransactionContext b = (TransactionContext)it.next();
/*  75:125 */         if (Configuration.isDebugLoggingEnabled()) {
/*  76:125 */           Configuration.logDebug(this + ": delegeting session close to " + b);
/*  77:    */         }
/*  78:126 */         b.sessionClosed();
/*  79:    */       }
/*  80:128 */       this.closed = true;
/*  81:129 */       if ((isTerminated()) && (!alreadyTerminated)) {
/*  82:129 */         notifyOfClosedEvent = true;
/*  83:    */       }
/*  84:    */     }
/*  85:132 */     if (notifyOfClosedEvent)
/*  86:    */     {
/*  87:133 */       if (Configuration.isDebugLoggingEnabled()) {
/*  88:133 */         Configuration.logDebug(this + ": all contexts terminated, firing TerminatedEvent");
/*  89:    */       }
/*  90:134 */       fireTerminatedEvent();
/*  91:    */     }
/*  92:    */   }
/*  93:    */   
/*  94:    */   public synchronized void notifyBeforeUse(CompositeTransaction ct, HeuristicMessage hmsg)
/*  95:    */     throws InvalidSessionHandleStateException
/*  96:    */   {
/*  97:151 */     if (this.closed) {
/*  98:151 */       throw new InvalidSessionHandleStateException("The underlying XA session is closed");
/*  99:    */     }
/* 100:    */     try
/* 101:    */     {
/* 102:156 */       TransactionContext suspended = null;
/* 103:157 */       if (ct != null)
/* 104:    */       {
/* 105:158 */         Iterator it = this.allContexts.iterator();
/* 106:159 */         while ((it.hasNext()) && (suspended == null))
/* 107:    */         {
/* 108:160 */           TransactionContext b = (TransactionContext)it.next();
/* 109:161 */           if (b.isSuspendedInTransaction(ct)) {
/* 110:162 */             suspended = b;
/* 111:    */           }
/* 112:    */         }
/* 113:    */       }
/* 114:167 */       if (suspended != null)
/* 115:    */       {
/* 116:168 */         if (Configuration.isInfoLoggingEnabled()) {
/* 117:168 */           Configuration.logInfo(this + ": resuming suspended XA context for transaction " + ct.getTid());
/* 118:    */         }
/* 119:169 */         this.currentContext = suspended;
/* 120:170 */         this.currentContext.transactionResumed();
/* 121:    */       }
/* 122:    */       else
/* 123:    */       {
/* 124:    */         try
/* 125:    */         {
/* 126:175 */           if (Configuration.isDebugLoggingEnabled()) {
/* 127:175 */             Configuration.logDebug(this + ": checking XA context for transaction " + ct);
/* 128:    */           }
/* 129:176 */           this.currentContext.checkEnlistBeforeUse(ct, hmsg);
/* 130:    */         }
/* 131:    */         catch (UnexpectedTransactionContextException txBoundaryPassed)
/* 132:    */         {
/* 133:180 */           if (Configuration.isInfoLoggingEnabled()) {
/* 134:180 */             Configuration.logInfo(this + ": suspending existing XA context and creating a new one for transaction " + ct);
/* 135:    */           }
/* 136:181 */           this.currentContext.transactionSuspended();
/* 137:182 */           this.currentContext = new TransactionContext(this.resource, this.xaResource);
/* 138:183 */           this.allContexts.add(this.currentContext);
/* 139:    */           try
/* 140:    */           {
/* 141:187 */             this.currentContext.checkEnlistBeforeUse(ct, hmsg);
/* 142:    */           }
/* 143:    */           catch (UnexpectedTransactionContextException e)
/* 144:    */           {
/* 145:189 */             String msg = "Unexpected error in session handle";
/* 146:190 */             Configuration.logWarning(msg, e);
/* 147:191 */             throw new InvalidSessionHandleStateException(msg);
/* 148:    */           }
/* 149:    */         }
/* 150:    */       }
/* 151:    */     }
/* 152:    */     catch (InvalidSessionHandleStateException e)
/* 153:    */     {
/* 154:197 */       notifySessionErrorOccurred();
/* 155:198 */       throw e;
/* 156:    */     }
/* 157:    */   }
/* 158:    */   
/* 159:    */   public boolean isErroneous()
/* 160:    */   {
/* 161:213 */     return this.erroneous;
/* 162:    */   }
/* 163:    */   
/* 164:    */   public void notifySessionErrorOccurred()
/* 165:    */   {
/* 166:224 */     this.erroneous = true;
/* 167:    */   }
/* 168:    */   
/* 169:    */   public void notifyTransactionTerminated(CompositeTransaction ct)
/* 170:    */   {
/* 171:236 */     boolean notifyOfTerminatedEvent = false;
/* 172:237 */     synchronized (this)
/* 173:    */     {
/* 174:238 */       boolean alreadyTerminated = isTerminated();
/* 175:239 */       Iterator it = this.allContexts.iterator();
/* 176:240 */       while (it.hasNext())
/* 177:    */       {
/* 178:241 */         TransactionContext b = (TransactionContext)it.next();
/* 179:242 */         b.transactionTerminated(ct);
/* 180:    */       }
/* 181:244 */       if ((isTerminated()) && (!alreadyTerminated)) {
/* 182:244 */         notifyOfTerminatedEvent = true;
/* 183:    */       }
/* 184:    */     }
/* 185:248 */     if (notifyOfTerminatedEvent)
/* 186:    */     {
/* 187:249 */       if (Configuration.isDebugLoggingEnabled()) {
/* 188:249 */         Configuration.logDebug(this + ": all contexts terminated, firing TerminatedEvent for " + this);
/* 189:    */       }
/* 190:250 */       fireTerminatedEvent();
/* 191:    */     }
/* 192:    */   }
/* 193:    */   
/* 194:    */   public void registerSessionHandleStateChangeListener(SessionHandleStateChangeListener listener)
/* 195:    */   {
/* 196:257 */     this.sessionHandleStateChangeListeners.add(listener);
/* 197:    */   }
/* 198:    */   
/* 199:    */   public void unregisterSessionHandleStateChangeListener(SessionHandleStateChangeListener listener)
/* 200:    */   {
/* 201:262 */     this.sessionHandleStateChangeListeners.remove(listener);
/* 202:    */   }
/* 203:    */   
/* 204:    */   private void fireTerminatedEvent()
/* 205:    */   {
/* 206:267 */     for (int i = 0; i < this.sessionHandleStateChangeListeners.size(); i++)
/* 207:    */     {
/* 208:268 */       SessionHandleStateChangeListener listener = (SessionHandleStateChangeListener)this.sessionHandleStateChangeListeners.get(i);
/* 209:269 */       listener.onTerminated();
/* 210:    */     }
/* 211:    */   }
/* 212:    */   
/* 213:    */   public String toString()
/* 214:    */   {
/* 215:275 */     return "a SessionHandleState with " + this.allContexts.size() + " context(s)";
/* 216:    */   }
/* 217:    */   
/* 218:    */   public boolean isActiveInTransaction(CompositeTransaction tx)
/* 219:    */   {
/* 220:285 */     boolean ret = false;
/* 221:286 */     if ((this.currentContext != null) && (tx != null)) {
/* 222:286 */       ret = this.currentContext.isInTransaction(tx);
/* 223:    */     }
/* 224:287 */     return ret;
/* 225:    */   }
/* 226:    */   
/* 227:    */   public boolean isInactiveInTransaction(CompositeTransaction tx)
/* 228:    */   {
/* 229:297 */     boolean ret = false;
/* 230:298 */     if ((this.currentContext != null) && (tx != null)) {
/* 231:298 */       ret = this.currentContext.isInactiveInTransaction(tx);
/* 232:    */     }
/* 233:299 */     return ret;
/* 234:    */   }
/* 235:    */ }


/* Location:           C:\myfile\mysoft\apache-maven-3.5.0-bin\apache-maven-3.5.0\myrep\com\atomikos\transactions-jta\3.7.0\transactions-jta-3.7.0.jar
 * Qualified Name:     com.atomikos.datasource.xa.session.SessionHandleState
 * JD-Core Version:    0.7.0.1
 */